package main

import (
	"fmt"
	"math"
)

func main() {
	//onion()
	r := &Context{}
	r.Use(middlewares1(), middlewares2(), middlewares3())

	r.Get("/r", func(c *Context) {
		fmt.Println("this is a get quest")
	})

	r.Run()
}

//设置一个常量，当HandlerFuns的长度大于该值时，就停止继续执行后面的hander
const abortIndex = math.MaxInt8 / 2

type HandlerFunc func(*Context)

type Context struct {
	handlerFuncs []HandlerFunc
	index        int8
}

//使用中间件方法
func (this *Context) Use(f ...HandlerFunc) {
	this.handlerFuncs = append(this.handlerFuncs, f...)
}

// 请求方法跟使用中间件方法主要是将handler函数添加到 切片中去
func (this *Context) Get(path string, f HandlerFunc) {
	this.handlerFuncs = append(this.handlerFuncs, f)
}

//模拟 next 函数
func (this *Context) Next() {
	if this.index < int8(len(this.handlerFuncs)) {
		this.index++
		this.handlerFuncs[this.index](this)
	}

}

//模拟abort函数
func (this *Context) Abort() {
	this.index = abortIndex
}

// 剥洋葱最外层
func (this *Context) Run() {
	this.handlerFuncs[0](this)
}

//中间价
func middlewares1() HandlerFunc {
	return func(c *Context) {
		fmt.Println("middle1 start")
		c.Next()
		fmt.Println("middle1 end")
	}

}

//中间价2
func middlewares2() HandlerFunc {
	return func(c *Context) {
		fmt.Println("middle2 start")
		c.Abort()
		fmt.Println("middle2 end")
	}

}

//中间价3
func middlewares3() HandlerFunc {
	return func(c *Context) {
		fmt.Println("middle3 start")
		c.Next()
		fmt.Println("middle3 end")
	}

}

//模拟洋葱模型
const flag = 10

func onion() {
	for i := 0; i < 4; i++ {
		i++
		fmt.Println("最外层开始")
		if flag > i { //next 函数
			i++
			func() {
				fmt.Println("第二层开始")
				i = 10 //模拟abort 函数
				if flag > i {
					func() {
						fmt.Println("最里层")
					}()
				}
				fmt.Println("第二层结束")
			}()
		}
		fmt.Println("最外层结束")
	}
}
